/* 
 * File:   main.c
 * Author: Twistx77
 *
 * Created on 21 de junio de 2012, 7:17
 */



#pragma config WDTEN = OFF          //WDT disabled (enabled by SWDTEN bit)
#pragma config PLLDIV = 2           //Divide by 2 (8 MHz oscillator input)
#pragma config STVREN = ON            //stack overflow/underflow reset enabled
#pragma config XINST = OFF         //Extended instruction set disabled
#pragma config CPUDIV = OSC2_PLL2          //Divided by 2 to provide 24Mhz Clock
#pragma config CP0 = OFF            //Program memory is not code-protected
#pragma config OSC = INTOSCPLL     //Internal Oscillator with PLL optional
#pragma config T1DIG = OFF          //Sec Osc clock source may not be selected, unless T1OSCEN = 1
#pragma config LPT1OSC = OFF        //high power Timer1 mode
#pragma config FCMEN = OFF          //Fail-Safe Clock Monitor disabled
#pragma config IESO = OFF           //Two-Speed Start-up disabled
#pragma config WDTPS = 32768        //1:32768
#pragma config DSWDTOSC = INTOSCREF //DSWDT uses INTOSC/INTRC as clock
#pragma config RTCOSC = T1OSCREF    //RTCC uses T1OSC/T1CKI as clock
#pragma config DSBOREN = OFF        //Zero-Power BOR disabled in Deep Sleep
#pragma config DSWDTEN = OFF        //Disabled
#pragma config DSWDTPS = 8192       //1:8,192 (8.5 seconds)
#pragma config IOL1WAY = OFF        //IOLOCK bit can be set and cleared
#pragma config MSSP7B_EN = MSK7     //7 Bit address masking
#pragma config WPFP = PAGE_1        //Write Protect Program Flash Page 0
#pragma config WPEND = PAGE_0       //Start protection at page 0
#pragma config WPCFG = OFF          //Write/Erase last page protect Disabled
#pragma config WPDIS = OFF          //WPFP[5:0], WPEND, and WPCFG bits ignored7



#include "../Headers/aUSBPS.h"

//Bootloader support code start
extern void _startup(void); // See c018i.c in your C18 compiler dir
#pragma code _RESET_INTERRUPT_VECTOR = 0x001000

void _reset(void) {
    _asm goto _startup _endasm
}
#pragma code

#define REMAPPED_RESET_VECTOR_ADDRESS		0x1000
#define REMAPPED_HIGH_INTERRUPT_VECTOR_ADDRESS	0x1008
#define REMAPPED_LOW_INTERRUPT_VECTOR_ADDRESS	0x1018


#pragma udata



void initializeSystem(void);

void main(void) {

    char USB_In_Buffer[64];
    UINT8 bytesReceived;
   
    initializeSystem();
    
    while (1) {
#if defined(USB_POLLING)
        // Check bus status and service USB interrupts.
        USBDeviceTasks(); // Interrupt or polling method.  If using polling, must call
        // this function periodically.  This function will take care
        // of processing and responding to SETUP transactions
        // (such as during the enumeration process when you first
        // plug in).  USB hosts require that USB devices should accept
        // and process SETUP packets in a timely fashion.  Therefore,
        // when using polling, this function should be called
        // regularly (such as once every 1.8ms or faster** [see
        // inline code comments in usb_device.c for explanation when
        // "or faster" applies])  In most cases, the USBDeviceTasks()
        // function does not take very long to execute (ex: <100
        // instruction cycles) before it returns.
#endif

//        if (x== 0){
//            USB_Out_Buffer[0]= 'H';
//            USB_Out_Buffer[1] = 'O';
//            USB_Out_Buffer[2] = 'L';
//            USB_Out_Buffer[3] = 'A';
//            putUSBUSART(&USB_Out_Buffer[0], 4);
//        }
//        x++;



        bytesReceived = getsUSBUSART(USB_In_Buffer, 10);
        if ((bytesReceived > 0) && (USB_In_Buffer[0] == 'S')){
            receivedUSBPacketHandler(&USB_In_Buffer[0]); //TODO: Check about the pointer warning.
        }
        bytesReceived = 0;

        //checkOutputStatus();

    }
}

void initializeSystem(void) {

    unsigned int pll_startup_counter;
    

    OSCCON = 0x60;
    OSCTUNEbits.PLLEN = 1; //Enable the PLL and wait 2+ms until the PLL locks before enabling USB module
    pll_startup_counter = 600;
    while (pll_startup_counter--);
    TRISAbits.TRISA7 = 0;
    PORTAbits.RA7 = 1;
    TRISAbits.TRISA6 = 0;

    initializeUSB();
    initializeRegulator();
}


/*
void UserInit(void)
{

    InitializeUSART();

// 	 Initialize the arrays
	


}//end UserInit

void InitializeUSART(void)
{
        unsigned char c;
       //TODO: CHECK THIS!
//        UART_TRISRx = 1;				// RX
//        UART_TRISTx = 0;				// TX

        TXSTA = 0x24;       	// TX enable BRGH=1
        RCSTA = 0x90;       	// Single Character RX
        SPBRG = 0x71;
        SPBRGH = 0x02;      	// 0x0271 for 48MHz -> 19200 baud
        BAUDCON = 0x08;     	// BRG16 = 1
        c = RCREG;				// read

}//end InitializeUSART

void putcUSART(char c)
{
    TXREG = c;
}


unsigned char getcUSART ()
{
        char  c;

        if (RCSTAbits.OERR)  // in case of overrun error
        {                    // we should never see an overrun error, but if we do,
                RCSTAbits.CREN = 0;  // reset the port
                c = RCREG;
                RCSTAbits.CREN = 1;  // and keep going.
        }
        else
                c = RCREG;
// not necessary.  EUSART auto clears the flag when RCREG is cleared
//	PIR1bits.RCIF = 0;    // clear Flag




        return c;
}

 */
//void ProcessIO(void)
//{
//    // User Application USB tasks
//    if((USBDeviceState < CONFIGURED_STATE)||(USBSuspendControl==1)) return;
//
//	if (RS232_Out_Data_Rdy == 0)  // only check for new USB buffer if the old RS232 buffer is
//	{						  // empty.  This will cause additional USB packets to be NAK'd
//		LastRS232Out = getsUSBUSART(RS232_Out_Data,64); //until the buffer is free.
//		if(LastRS232Out > 0)
//		{
//			RS232_Out_Data_Rdy = 1;  // signal buffer full
//			RS232cp = 0;  // Reset the current position
//		}
//	}
//
//    //Check if one or more bytes are waiting in the physical UART transmit
//    //queue.  If so, send it out the UART TX pin.
//	if(RS232_Out_Data_Rdy && mTxRdyUSART())
//	{
//    	#if defined(USB_CDC_SUPPORT_HARDWARE_FLOW_CONTROL)
//        	//Make sure the receiving UART device is ready to receive data before
//        	//actually sending it.
//        	if(UART_CTS == USB_CDC_CTS_ACTIVE_LEVEL)
//        	{
//        		putcUSART(RS232_Out_Data[RS232cp]);
//        		++RS232cp;
//        		if (RS232cp == LastRS232Out)
//        			RS232_Out_Data_Rdy = 0;
//    	    }
//	    #else
//	        //Hardware flow control not being used.  Just send the data.
//    		putcUSART(RS232_Out_Data[RS232cp]);
//    		++RS232cp;
//    		if (RS232cp == LastRS232Out)
//    			RS232_Out_Data_Rdy = 0;
//	    #endif
//	}
//
//    //Check if we received a character over the physical UART, and we need
//    //to buffer it up for eventual transmission to the USB host.
//	if(mDataRdyUSART() && (NextUSBOut < (CDC_DATA_OUT_EP_SIZE - 1)))
//	{
//		USB_Out_Buffer[NextUSBOut] = getcUSART();
//		++NextUSBOut;
//		USB_Out_Buffer[NextUSBOut] = 0;
//	}
//
//	#if defined(USB_CDC_SUPPORT_HARDWARE_FLOW_CONTROL)
//    	//Drive RTS pin, to let UART device attached know if it is allowed to
//    	//send more data or not.  If the receive buffer is almost full, we
//    	//deassert RTS.
//    	if(NextUSBOut <= (CDC_DATA_OUT_EP_SIZE - 5u))
//    	{
//            UART_RTS = USB_CDC_RTS_ACTIVE_LEVEL;
//        }
//        else
//        {
//        	UART_RTS = (USB_CDC_RTS_ACTIVE_LEVEL ^ 1);
//        }
//    #endif
//
//    //Check if any bytes are waiting in the queue to send to the USB host.
//    //If any bytes are waiting, and the endpoint is available, prepare to
//    //send the USB packet to the host.
//	if((USBUSARTIsTxTrfReady()) && (NextUSBOut > 0))
//	{
//		putUSBUSART(&USB_Out_Buffer[0], NextUSBOut);
//		NextUSBOut = 0;
//	}
//
//    CDCTxService();
//
//}//end ProcessIO









